package com.xc.common.tool;

import io.micrometer.core.instrument.util.StringUtils;
import org.apache.poi.xwpf.usermodel.*;
import org.jetbrains.annotations.NotNull;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.nodes.Node;
import org.jsoup.select.Elements;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTTblWidth;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTTcPr;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STMerge;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.STTblWidth;

import java.math.BigInteger;
import java.util.*;

public class WordUtil {

    public static void handleTableHtml(XWPFDocument pdocument,String tableHtmlStr){

        String simpleTableHtml = simplifyTable(tableHtmlStr);
        Document tableDoc = Jsoup.parse(simpleTableHtml);
        Elements trList = tableDoc.getElementsByTag("tr");
        Elements tdList = trList.get(0).getElementsByTag("td");
        XWPFTable xwpfTable = pdocument.createTable(trList.size(),tdList.size());
        Map<String,Boolean>[][] array = new Map[trList.size()][tdList.size()];
        for (int row = 0; row < trList.size(); row++) {
            Element trElement = trList.get(row);
            Elements tds = trElement.getElementsByTag("td");
            for (int col = 0; col < tds.size(); col++) {
                Element colElement = tds.get(col);
                String colspan = colElement.attr("colspan");
                String rowspan = colElement.attr("rowspan");
                String style = colElement.attr("style");
                StringBuilder styleSB = new StringBuilder();
                try {
                    if(StringUtils.isNotEmpty(colspan)){
                        int colCount = Integer.parseInt(colspan);
                        for (int i = 0; i < colCount-1; i++) {
                            array[row][col+i+1] = new HashMap<>();
                            array[row][col+i+1].put("mergeCol",true);
                        }
                    }
                } catch (NumberFormatException e) {
                }
                if(StringUtils.isNotEmpty(rowspan)){
                    int rowCount = Integer.valueOf(rowspan);
                    for (int i = 0; i < rowCount; i++) {
                        array[row+i+1][col] = new HashMap<>();
                        array[row+i+1][col].put("mergeRow",true);
                    }
                }
                XWPFTableCell tableCell = xwpfTable.getRow(row).getCell(col);
//                tableCell.setWidth("2000");
                if(StringUtils.isEmpty(colspan)){
                    if(col==0){
                        if(tableCell.getCTTc().getTcPr()==null){
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                            tcPr.addNewHMerge().setVal(STMerge.RESTART);
                        }else{
                            if(tableCell.getCTTc().getTcPr().getHMerge()==null){
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.addNewHMerge().setVal(STMerge.RESTART);
                            }else {
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.getHMerge().setVal(STMerge.RESTART);
                            }
                        }
                    }else {
                        if(array[row][col]!=null && array[row][col].get("mergeCol")!=null && array[row][col].get("mergeCol")){
                            if(tableCell.getCTTc().getTcPr()==null){
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                                tcPr.addNewHMerge().setVal(STMerge.CONTINUE);
                            }else {
                                if(tableCell.getCTTc().getTcPr().getHMerge()==null){
                                    CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                    tcPr.addNewHMerge().setVal(STMerge.CONTINUE);
                                }else {
                                    CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                    tcPr.getHMerge().setVal(STMerge.CONTINUE);
                                }

                            }
                            continue;
                        }else {
                            if(tableCell.getCTTc().getTcPr()==null){
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                                tcPr.addNewHMerge().setVal(STMerge.RESTART);
                            }else {
                                if(tableCell.getCTTc().getTcPr().getHMerge()==null){
                                    CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                    tcPr.addNewHMerge().setVal(STMerge.RESTART);
                                }else{
                                    CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                    tcPr.getHMerge().setVal(STMerge.RESTART);
                                }

                            }
                        }
                    }
                }else {
                    if(tableCell.getCTTc().getTcPr()==null){
                        CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                        tcPr.addNewHMerge().setVal(STMerge.RESTART);
                    }else {
                        if(tableCell.getCTTc().getTcPr().getHMerge()==null){
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                            tcPr.addNewHMerge().setVal(STMerge.RESTART);
                        }else{
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                            tcPr.getHMerge().setVal(STMerge.RESTART);
                        }
                    }
                }
                if(StringUtils.isEmpty(rowspan)){
                    if(array[row][col]!=null && array[row][col].get("mergeRow")!=null && array[row][col].get("mergeRow")){
                        if(tableCell.getCTTc().getTcPr()==null){
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                            tcPr.addNewVMerge().setVal(STMerge.CONTINUE);
                        }else {
                            if(tableCell.getCTTc().getTcPr().getVMerge()==null){
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.addNewVMerge().setVal(STMerge.CONTINUE);
                            }else {
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.getVMerge().setVal(STMerge.CONTINUE);
                            }
                        }
                        continue;
                    }else {
                        if(tableCell.getCTTc().getTcPr()==null){
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                            tcPr.addNewVMerge().setVal(STMerge.RESTART);
                        }else {
                            if(tableCell.getCTTc().getTcPr().getVMerge()==null){
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.addNewVMerge().setVal(STMerge.RESTART);
                            }else {
                                CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                                tcPr.getVMerge().setVal(STMerge.RESTART);
                            }
                        }
                    }
                }else{
                    if(tableCell.getCTTc().getTcPr()==null){
                        CTTcPr tcPr = setPrWidth(tableCell.getCTTc().addNewTcPr(),1000);
                        tcPr.addNewVMerge().setVal(STMerge.RESTART);
                    }else {
                        if(tableCell.getCTTc().getTcPr().getVMerge()==null){
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                            tcPr.addNewVMerge().setVal(STMerge.RESTART);
                        }else {
                            CTTcPr tcPr = setPrWidth(tableCell.getCTTc().getTcPr(),1000);
                            tcPr.getVMerge().setVal(STMerge.RESTART);
                        }
                    }
                }
                tableCell.removeParagraph(0);
                XWPFParagraph paragraph = tableCell.addParagraph();
                paragraph.setStyle(styleSB.toString());
                if(!StringUtils.isEmpty(style) && style.contains("text-align:center")){
                    paragraph.setAlignment(ParagraphAlignment.CENTER);
                    paragraph.setStyle("width:77.4000pt;border-left:none");

                }
                XWPFRun xwpfRun = paragraph.createRun();
                xwpfRun.setFontSize(12);
                xwpfRun.setFontFamily("宋体");
                xwpfRun.setFontFamily("Times New Roman");
                xwpfRun.setText(colElement.text());
            }
        }

    }
    private XWPFRun getTextRun(XWPFParagraph paragraph){
        XWPFRun xwpfRun = paragraph.createRun();
        xwpfRun.setFontSize(12);
        xwpfRun.setFontFamily("宋体");
        xwpfRun.setFontFamily("Times New Roman");
        return xwpfRun;
    }
    @NotNull
    private static CTTcPr setPrWidth(CTTcPr tableCell,Integer width) {
        CTTcPr tcPr = tableCell;
        CTTblWidth tblWidth = tcPr.addNewTcW();
        tblWidth.setType(STTblWidth.DXA);
        tblWidth.setW(BigInteger.valueOf(width));
        return tcPr;
    }

    public static String simplifyTable   (String  tableContent)   {
        if(tableContent==null||tableContent.isEmpty()){
            return null;
        }
        Document tableDoc = Jsoup.parse(tableContent);
        Elements trElements = tableDoc.getElementsByTag("tr");
        if(trElements==null){
            return null;
        }
        Iterator<Element> eleIterator = trElements.iterator();
        int rowNum = 0;
        //针对colspan操作
        while (eleIterator.hasNext()){
            rowNum++;
            Element trElement = eleIterator.next();
            //去除所有样式
            trElement.removeAttr("class");
            Elements tdElements = trElement.getElementsByTag("td");
            List<Element> tdEleList = convertElements2List(tdElements);
            for (int i = 0; i < tdEleList.size(); i++) {
                Element curElement = tdEleList.get(i);
                //去除所有样式
                curElement.removeAttr("class");
                Element ele = curElement.clone();
                String colspanVarStr = curElement.attr("colspan");
                try {
                    if(colspanVarStr!=null&&!colspanVarStr.isEmpty()){
                        ele.removeAttr("colspan");
                        int colspanVal = Integer.valueOf(colspanVarStr);
                        for(int k=0;k<colspanVal-1;k++){
                            curElement.after(ele.outerHtml());
                        }
                    }
                } catch (NumberFormatException e) {

                }
            }
        }
        //针对rowspan操作
        List<Element> trEleList = convertElements2List(trElements);
        Element firstTrEle = trElements.first();
        Elements tdElements = firstTrEle.getElementsByTag("td");
        int tdCount = tdElements.size();
        for (int i = 0; i < tdElements.size(); i++) {//获取该列下所有单元格
            for (Element trElement : trEleList) {
                List<Element> tdElementList = convertElements2List(trElement.getElementsByTag("td"));
                try{
                    tdElementList.get(i);
                }catch (Exception e){
                    continue;
                }
                Node curTdNode = tdElementList.get(i);
                Node cNode = curTdNode.clone();
                String rowspanValStr = curTdNode.attr("rowspan");
                if(StringUtils.isNotEmpty(rowspanValStr)){
                    cNode.removeAttr("rowspan");
                    Element nextTrElement = trElement.nextElementSibling();
                    int rowspanVal = Integer.parseInt(rowspanValStr);
                    for(int j=0;j<rowspanVal-1;j++){
                        Node tempNode = cNode.clone();
                        List<Node> nodeList = new ArrayList<>();
                        nodeList.add(tempNode);
                        if(j>0){
                            nextTrElement = nextTrElement.nextElementSibling();
                            int indexNum = i + 1;
                            if(i==0){
                                indexNum = 0;
                            }
                            if(indexNum==tdCount){
                                nextTrElement.appendChild(tempNode);
                            }else{
                                nextTrElement.insertChildren(indexNum,nodeList);
                            }
                        }
                    }
                }
            }
        }
        Element tableEle = tableDoc.getElementsByTag("table").first();
        String tableHtml = tableEle.outerHtml();
        return tableHtml;
    }
    private static List<Element> convertElements2List(Elements curElements){
        List<Element> elementList = new ArrayList<>();
        Iterator<Element> elementIterator = curElements.iterator();
        while (elementIterator.hasNext()){
            Element element = elementIterator.next();
            elementList.add(element);
        }
        return elementList;
    }
}
